#ifndef STBI_INCLUDE_STB_IMAGE_H
#define STBI_INCLUDE_STB_IMAGE_H

#ifndef STBI_NO_STDIO

#if defined(_MSC_VER) && _MSC_VER >= 1400
#define _CRT_SECURE_NO_WARNINGS // suppress warnings about fopen()
#pragma warning(push)
#pragma warning(disable:4996) // suppress even more warnings about fopen()
#endif
#include <stdio.h>
#endif // STBI_NO_STDIO

#define STBI_VERSION 1

enum
{
	STBI_default = 0, // only used for req_comp

	STBI_grey = 1,
	STBI_grey_alpha = 2,
	STBI_rgb = 3,
	STBI_rgb_alpha = 4
};

typedef unsigned char stbi_uc;

#ifdef __cplusplus
extern "C" {
#endif

#ifdef STB_IMAGE_STATIC
#define STBIDEF static
#else
#define STBIDEF extern
#endif

	//////////////////////////////////////////////////////////////////////////////
	//
	// PRIMARY API - works on images of any type
	//

	//
	// load image by filename, open file, or memory buffer
	//

	STBIDEF stbi_uc *stbi_load_from_memory(stbi_uc const *buffer, int len, int *x, int *y, int *comp, int req_comp);

#ifndef STBI_NO_STDIO
	STBIDEF stbi_uc *stbi_load (char const *filename, int *x, int *y, int *comp, int req_comp);
	STBIDEF stbi_uc *stbi_load_from_file (FILE *f, int *x, int *y, int *comp, int req_comp);
	// for stbi_load_from_file, file pointer is left pointing immediately after image
#endif

	typedef struct
	{
		int (*read) (void *user,char *data,int size); // fill 'data' with 'size' bytes. return number of bytes actually read
		void (*skip) (void *user,int n); // skip the next 'n' bytes, or 'unget' the last -n bytes if negative
		int (*eof) (void *user); // returns nonzero if we are at end of file/data
	} stbi_io_callbacks;

	STBIDEF stbi_uc *stbi_load_from_callbacks (stbi_io_callbacks const *clbk, void *user, int *x, int *y, int *comp, int req_comp);

#ifndef STBI_NO_HDR
	STBIDEF float *stbi_loadf_from_memory(stbi_uc const *buffer, int len, int *x, int *y, int *comp, int req_comp);

#ifndef STBI_NO_STDIO
	STBIDEF float *stbi_loadf (char const *filename, int *x, int *y, int *comp, int req_comp);
	STBIDEF float *stbi_loadf_from_file (FILE *f, int *x, int *y, int *comp, int req_comp);
#endif

	STBIDEF float *stbi_loadf_from_callbacks (stbi_io_callbacks const *clbk, void *user, int *x, int *y, int *comp, int req_comp);

	STBIDEF void stbi_hdr_to_ldr_gamma(float gamma);
	STBIDEF void stbi_hdr_to_ldr_scale(float scale);

	STBIDEF void stbi_ldr_to_hdr_gamma(float gamma);
	STBIDEF void stbi_ldr_to_hdr_scale(float scale);
#endif // STBI_NO_HDR

	// stbi_is_hdr is always defined
	STBIDEF int stbi_is_hdr_from_callbacks(stbi_io_callbacks const *clbk, void *user);
	STBIDEF int stbi_is_hdr_from_memory(stbi_uc const *buffer, int len);
#ifndef STBI_NO_STDIO
	STBIDEF int stbi_is_hdr (char const *filename);
	STBIDEF int stbi_is_hdr_from_file(FILE *f);
#endif // STBI_NO_STDIO


	// get a VERY brief reason for failure
	// NOT THREADSAFE
	STBIDEF const char *stbi_failure_reason (void);

	// free the loaded image -- this is just free()
	STBIDEF void stbi_image_free (void *retval_from_stbi_load);

	// get image dimensions & components without fully decoding
	STBIDEF int stbi_info_from_memory(stbi_uc const *buffer, int len, int *x, int *y, int *comp);
	STBIDEF int stbi_info_from_callbacks(stbi_io_callbacks const *clbk, void *user, int *x, int *y, int *comp);

#ifndef STBI_NO_STDIO
	STBIDEF int stbi_info (char const *filename, int *x, int *y, int *comp);
	STBIDEF int stbi_info_from_file (FILE *f, int *x, int *y, int *comp);

#endif



	// for image formats that explicitly notate that they have premultiplied alpha,
	// we just return the colors as stored in the file. set this flag to force
	// unpremultiplication. results are undefined if the unpremultiply overflow.
	STBIDEF void stbi_set_unpremultiply_on_load(int flag_true_if_should_unpremultiply);

	// indicate whether we should process iphone images back to canonical format,
	// or just pass them through "as-is"
	STBIDEF void stbi_convert_iphone_png_to_rgb(int flag_true_if_should_convert);


	// ZLIB client - used by PNG, available for other purposes

	STBIDEF char *stbi_zlib_decode_malloc_guesssize(const char *buffer, int len, int initial_size, int *outlen);
	STBIDEF char *stbi_zlib_decode_malloc_guesssize_headerflag(const char *buffer, int len, int initial_size, int *outlen, int parse_header);
	STBIDEF char *stbi_zlib_decode_malloc(const char *buffer, int len, int *outlen);
	STBIDEF int stbi_zlib_decode_buffer(char *obuffer, int olen, const char *ibuffer, int ilen);

	STBIDEF char *stbi_zlib_decode_noheader_malloc(const char *buffer, int len, int *outlen);
	STBIDEF int stbi_zlib_decode_noheader_buffer(char *obuffer, int olen, const char *ibuffer, int ilen);


	// define faster low-level operations (typically SIMD support)
#ifdef STBI_SIMD
	typedef void (*stbi_idct_8x8)(stbi_uc *out, int out_stride, short data[64], unsigned short *dequantize);
	// compute an integer IDCT on "input"
	// input[x] = data[x] * dequantize[x]
	// write results to 'out': 64 samples, each run of 8 spaced by 'out_stride'
	// CLAMP results to 0..255
	typedef void (*stbi_YCbCr_to_RGB_run)(stbi_uc *output, stbi_uc const *y, stbi_uc const *cb, stbi_uc const *cr, int count, int step);
	// compute a conversion from YCbCr to RGB
	// 'count' pixels
	// write pixels to 'output'; each pixel is 'step' bytes (either 3 or 4; if 4, write '255' as 4th), order R,G,B
	// y: Y input channel
	// cb: Cb input channel; scale/biased to be 0..255
	// cr: Cr input channel; scale/biased to be 0..255

	STBIDEF void stbi_install_idct(stbi_idct_8x8 func);
	STBIDEF void stbi_install_YCbCr_to_RGB(stbi_YCbCr_to_RGB_run func);
#endif // STBI_SIMD


#ifdef __cplusplus
}
#endif

#ifndef STB_IMAGE_IMPLEMENTATION
#define STB_IMAGE_IMPLEMENTATION
#endif

#endif